<template>
  <view class="evaluate-container" :style="{ overflow: showPopup ? 'hidden' : 'visible' }">
    <view class="evaluate-score">
      <view class="score-wrapper">
        <view class="score-analyze">
          <view class="score">{{ score }}</view>
          <view class="analyze" @click="handlePopUp">音素分析</view>
        </view>
        <view class="score-content" v-if="Array.isArray(evaluate.analysis.wordsDetail)">
          <wordNote v-for="(item, index) in evaluate.analysis.wordsDetail" :key="index + item.lab" :word="item" />
          <image class="tonescore-image" :src="evaluate.analysis.wordsDetail.slice(-1).tonescore == 1
    ? 'https://rwstatic.tentons.cn/web/Lesson/images/tonescore-up.png'
    : 'https://rwstatic.tentons.cn/web/Lesson/images/tonescore-down.png'
    " />
        </view>
      </view>
      <view class="score-desc">
        <view class="desc-item mr ml">
          <view class="desc-tag awesome"></view>
          <text class="desc-label">Awesome</text>
        </view>
        <view class="desc-item mr">
          <view class="desc-tag good"></view>
          <text class="desc-label">Good</text>
        </view>
        <view class="desc-item mr">
          <view class="desc-tag average"></view>
          <text class="desc-label">Average</text>
        </view>
        <view class="desc-item mr">
          <view class="desc-tag wrong"></view>
          <text class="desc-label">Wrong</text>
        </view>
        <view class="desc-item mr ml">
          <view class="desc-stress"></view>
          <text class="desc-label">stress</text>
        </view>
        <view class="desc-item mr">
          <image class="desc-image" src="https://rwstatic.tentons.cn/web/Lesson/images/tonescore-up.png" />
          <text class="desc-label">rising intonation</text>
        </view>
        <view class="desc-item">
          <image class="desc-image" src="https://rwstatic.tentons.cn/web/Lesson/images/tonescore-down.png" />
          <text class="desc-label">falling intonation</text>
        </view>
      </view>
    </view>
    <view class="evaluate-sentence" :style="pageType == 'freeTalk' && { minHeight: 'auto' }">
      <view class="evaluate-sentence-wrapper">
        <view class="sentence-title">整句分析</view>
        <view class="sentence-row">
          <view class="col-content">
            <text class="score">{{ evaluate.analysis.fluency_overall }}</text>
            <text class="desc">流利度</text>
          </view>
          <view class="col-content">
            <text class="score">{{ evaluate.analysis.integrity }}</text>
            <text class="desc">完整度</text>
          </view>
          <view class="col-content">
            <text class="score">{{ evaluate.analysis.accuracy ? evaluate.analysis.accuracy : "— —" }}</text>
            <text class="desc">准确度</text>
          </view>
        </view>

        <view class="sentence-title">朗读分析</view>
        <view class="sentence-info">
          <view class="info-list">
            <view class="list-label">录音</view>
            <loudspeaker class="list-speaker" :voice="evaluate.user_voice" />
          </view>
          <block v-for="item in infoList" :key="item.id">
            <template v-if="pageType == 'freeTalk' && [1, 2, 3].includes(item.id)"></template>
            <template v-else>
              <view class="info-list" >
                <view class="list-label">{{ item.label }}</view>
                <view :class="['list-desc', [1, 2, 3].includes(item.id) && item.desc !== '无' ? 'error' : '']">
                  {{ item.desc }}
                </view>
              </view>
            </template>
          </block>
        </view>
        <view class="h12"></view>
        <image class="sentence-status" src="https://rwstatic.tentons.cn/web/Lesson/images/sentence-end-status.png" />
        <view class="h20"></view>
        <view class="tag"></view>
      </view>
    </view>
    <view class="evaluate-line"></view>

    <uni-popup ref="popupRef" type="bottom" :safe-area="false" :mask-click="false">
      <view class="evaluate-popup-content">
        <image class="popup-close" src="https://rwstatic.tentons.cn/web/Lesson/images/close-icon.png"
          @click="handleClosePopup" />
        <view class="popup-title">
          音素分析
          <text class="popup-title-label">点击单词切换查看音素详细解析</text>
        </view>
        <view class="popup-words">
          <view class="word" v-for="(item, index) in evaluate.analysis.wordsDetail" :key="index + item.lab"
            @click="handleActiveWord(item, index)">
            <wordNote :word="item" :show-score="false" :show-under-line="false"
              :show-active="activeIndex === index ? true : false" />
          </view>
        </view>
        <view class="popup-sound">
          <view class="sound-row">
            标准发音：{{ standardWord.word }}
            <text class="sound">{{ standardWord.sound }}</text>
          </view>
          <view class="sound-row">
            你的发音：{{ userWord.word }}
            <rich-text class="sound" :nodes="userWord.sound"></rich-text>
          </view>
        </view>
        <view class="popup-label">
          <view class="label-item" v-for="item in labelList" :key="item.label">
            <view :class="['label-tag', item.label]"></view>
            <text class="label-text">{{ item.label }}</text>
          </view>
        </view>
        <view class="popup-line"></view>
      </view>
    </uni-popup>
  </view>

  <CwCommon />
</template>

<script setup lang="ts">
import { ref, onMounted } from "vue";
import wordNote from "./wordNote.vue";
import loudspeaker from "@/components/loudspeaker.vue";
import { startEvaluating } from "@/utils/chivox";
// @ts-ignore
import { ossDownLoad } from "@/utils/oss/oss.js";
import API from "@/api";
import { util } from "@/utils/util";

interface IEvaluate {
  score?: number;
  [x: string]: any;
}

const props = defineProps({
  pageType: {
    type: String,
    default: ''
  }
})

const emits = defineEmits<{
  (e: "init"): void;
}>();

const fs = uni.getFileSystemManager();

const showPopup = ref(false);
const evaluate = ref<IEvaluate>({
  score: 0,
  analysis: {
    wordsDetail: [],
  },
});
const activeIndex = ref(0);
const standardWord = ref({
  word: "",
  sound: "",
});
const userWord = ref({
  word: "",
  sound: [],
});
const labelList = ref([
  {
    label: "Awesome",
  },
  {
    label: "Good",
  },
  {
    label: "Average",
  },
  {
    label: "Wrong",
  },
]);

const popupRef = ref<any>(null);
const infoList = ref([
  {
    id: 1,
    label: "多读",
    desc: "",
  },
  {
    id: 2,
    label: "漏读",
    desc: "",
  },
  {
    id: 3,
    label: "错读",
    desc: "",
  },
  {
    id: 4,
    label: "停顿次数",
    desc: "",
  },
  {
    id: 5,
    label: "录音语速",
    desc: "",
  },
]);
const section_id = ref("");
const score = ref(0);

// 基础课音素修复
const handleRepairPhoneme = async (item: any) => {
  return new Promise<void>((resolve, reject) => {
    util.showLoading();
    ossDownLoad(item.user_voice, false).then((oss: { data: any; }) => {
      fs.readFile({
        filePath: oss.data,
        success: (file) => {
          startEvaluating({
            evaluatingInfo: { sentence: item.sentences, isPhoneme: true },
            audioBuffer: file.data as ArrayBuffer,
            onSuccess: (eva) => {
              API.repairPhoneme({
                section_id: section_id.value,
                type: item.type,
                record_id: item.record_id,
                analysis: JSON.stringify(eva),
                thirdParty: "chevon",
              }).then(async res => {
                evaluate.value = res;
                uni.setStorageSync(`${item.record_id}`, JSON.stringify(res));
                util.hideLoading();

                resolve();
              })
            },
            onError: (errMsg) => {
              console.log(errMsg);
              util.showDialogue(errMsg);
              util.hideLoading();

              reject();
            },
          })
        },
        fail: (errMsg) => {
          console.log(errMsg);
          util.hideLoading();
          util.showDialogue("找不到音频文件");
          reject();
        }
      })
    })
  })
}

const handlePopUp = async () => {
  if (!(Array.isArray(evaluate.value.analysis.phoneme) && evaluate.value.analysis.phoneme.length)) {
    await handleRepairPhoneme(evaluate.value);
  }

  const phoneme = evaluate.value.analysis.phoneme;
  if (!phoneme || !phoneme.length) {
    return;
  }

  handleSetStandardWord(phoneme[0]);

  showPopup.value = true;
  popupRef.value?.open("bottom");
};

const handleSetStandardWord = (word: { phone_str: string; char: string; phone: any[] }) => {
  standardWord.value.sound = word.phone_str;
  standardWord.value.word = word.char;
  userWord.value.word = word.char;

  let soundColor = "";
  let childrenNodes: any[] = [
    {
      name: "span",
      attrs: {
        class: "rich-text_tag",
      },
      children: [
        {
          type: "text",
          text: "[",
        },
      ],
    },
  ];
  word.phone.forEach((item) => {
    if (item.score >= 0 && item.score <= 40) {
      soundColor = "rich-text_040";
    } else if (item.score >= 41 && item.score <= 59) {
      soundColor = "rich-text_4159";
    } else if (item.score >= 60 && item.score <= 79) {
      soundColor = "rich-text_6079";
    } else if (item.score >= 80 && item.score <= 100) {
      soundColor = "rich-text_80100";
    }

    childrenNodes.push({
      name: "span",
      attrs: {
        class: soundColor,
      },
      children: [
        {
          type: "text",
          text: item.char,
        },
      ],
    });
  });

  childrenNodes.push({
    name: "span",
    attrs: {
      class: "rich-text_tag",
    },
    children: [
      {
        type: "text",
        text: "]",
      },
    ],
  });

  userWord.value.sound = [
    {
      name: "div",
      attrs: {
        class: "rich-text_sentence",
      },
      children: childrenNodes,
    },
  ] as any;
};

const handleClosePopup = () => {
  showPopup.value = false;
  popupRef.value?.close();
};

const handleInit = (data: any, sectionId: string) => {
  evaluate.value = data;
  score.value = data.score;
  section_id.value = sectionId;
  const analysisInfo = data.analysis;

  infoList.value[0].desc = analysisInfo.readMore.length ? analysisInfo.readMore.join() : "无";
  infoList.value[1].desc = analysisInfo.MissedRead.length ? analysisInfo.MissedRead.join() : "无";
  infoList.value[2].desc = analysisInfo.misread.length ? analysisInfo.misread.join() : "无";
  infoList.value[3].desc = analysisInfo.fluency_pause ? `${analysisInfo.fluency_pause}次` : "无";
  infoList.value[4].desc = analysisInfo.fluency_speed ? `${analysisInfo.fluency_speed}词/分钟` : "无";
};

const handleActiveWord = (item: any, index: number) => {
  if (item.type === 2) {
    return;
  }
  activeIndex.value = index;

  const phoneme = evaluate.value.analysis.phoneme;
  const curWord = phoneme.find((val: { char: string }) => val.char.toLocaleLowerCase() === item.lab.toLocaleLowerCase());
  handleSetStandardWord(curWord);
};

defineExpose({
  handleInit,
});

onMounted(() => {
  emits("init");
})
</script>

<style scoped lang="scss">
.evaluate-container {
  width: 100%;
  height: 100%;

  .evaluate-score {
    position: relative;
    width: 100%;

    .score-wrapper {
      display: flex;
      align-items: center;
      padding: 1.3rem 2.2rem 1.8rem;
      border-radius: 1.5rem;
      background-color: #ffffff;

      .score-analyze {
        display: flex;
        flex-direction: column;
        align-items: center;
        width: 6rem;
        margin-right: 2.1rem;

        .score {
          display: flex;
          align-items: center;
          justify-content: center;
          margin-bottom: 0.8rem;
          width: 5rem;
          height: 5rem;
          font-size: 2.2rem;
          font-family: baloo;
          color: #ffffff;
          background-image: url("https://rwstatic.tentons.cn/web/Lesson/images/score-wrapper.png");
          background-size: contain;
          background-repeat: no-repeat;
        }

        .analyze {
          display: flex;
          align-items: center;
          justify-content: center;
          width: 6rem;
          height: 1.8rem;
          font-size: 1.1rem;
          font-family: xiaolai;
          color: #ffffff;
          border-radius: 1rem;
          background-color: #7eb6e6;
        }
      }

      .score-content {
        flex: 1;

        .tonescore-image {
          width: 2rem;
          height: 2rem;
        }
      }
    }

    .score-desc {
      display: flex;
      flex-wrap: wrap;
      width: 33.5rem;
      height: 6rem;
      margin: 0 auto 1.7rem;
      padding: 1.1rem 0 0;
      border-radius: 1rem;
      background-color: rgba(#fae4bd, 0.2);

      .desc-item {
        display: flex;
        height: 2rem;
        margin-bottom: 1rem;
        align-items: center;

        .desc-tag {
          width: 1rem;
          height: 1rem;
          margin-right: 0.4rem;
          border-radius: 50%;
        }

        .desc-stress {
          width: 1.5rem;
          height: 2px;
          margin-right: 0.4rem;
          background-color: #e8a71b;
        }

        .desc-image {
          width: 2rem;
          height: 2rem;
          margin-right: 0.1rem;
        }

        .desc-label {
          font-size: 1.2rem;
          font-family: xiaolai;
          color: $uni-text-color-grey;
        }

        .awesome {
          background-color: #b0bd3b;
        }

        .good {
          background-color: #7eb6e6;
        }

        .average {
          background-color: #ffaf00;
        }

        .wrong {
          background-color: $uni-text-color-error;
        }
      }

      .mr {
        margin-right: 2.4rem;
      }

      .ml {
        margin-left: 1.3rem;
      }
    }
  }

  .evaluate-sentence {
    width: 32.5rem;
    min-height: 47rem;
    margin: 0 auto 2rem;
    padding: 0.5rem;
    border-radius: 1.5rem;
    border: 1.5px solid #d8ab61;
    background-color: #f9f4e0;

    .evaluate-sentence-wrapper {
      position: relative;
      padding-top: 2rem;
      border-radius: 1.5rem;
      background-color: #ffffff;

      .sentence-title {
        display: flex;
        align-items: center;
        justify-content: center;
        width: 7.5rem;
        height: 1.8rem;
        margin: 0 auto 1.8rem;
        font-family: xiaolai;
        font-size: 1.7rem;
        color: $uni-text-color;
        background-image: url("https://rwstatic.tentons.cn/web/Lesson/images/sentence-text.png");
        background-size: contain;
        background-repeat: no-repeat;
      }

      .sentence-row {
        display: flex;
        justify-content: space-evenly;
        margin-bottom: 1rem;

        .col-content {
          display: flex;
          align-items: center;
          flex-direction: column;
          width: 10rem;
          height: 7.4rem;
          background-image: url("https://rwstatic.tentons.cn/web/Lesson/images/sentence-col.png");
          background-size: contain;
          background-repeat: no-repeat;

          .score {
            margin-top: 1.2rem;
            margin-bottom: 1rem;
            line-height: 1;
            font-family: baloo;
            font-size: 2.4rem;
            color: $uni-text-color;
          }

          .desc {
            font-family: xiaolai;
            font-size: 1.4rem;
            color: $uni-text-color-minor;
          }
        }
      }

      .sentence-desc {
        display: block;
        margin-bottom: 1.7rem;
        text-align: center;
        font-family: xiaolai;
        font-size: 1.2rem;
        color: $uni-text-color-grey;
      }

      .sentence-info {
        padding: 0 2rem;

        .info-list {
          display: flex;
          align-items: center;
          justify-content: space-between;
          width: 28.5rem;
          padding: 1rem 0;
          border-bottom: 1px solid #faefde;

          .list-label {
            width: 6rem;
            font-family: xiaolai;
            font-size: 1.4rem;
            color: $uni-text-color;
          }

          .list-desc {
            flex: 1;
            text-align: right;
            font-family: xiaolai;
            font-size: 1.4rem;
            color: $uni-text-color;
            word-break: break-all;
          }

          .list-speaker {
            width: 3.1rem;
            height: 3.1rem;
          }

          .error {
            color: $uni-text-color-error;
          }
        }

        .info-list:last-child {
          border-bottom: none;
        }
      }

      .h12 {
        height: 1.2rem;
      }

      .h20 {
        height: 2rem;
      }

      .sentence-status {
        display: flex;
        justify-content: center;
        margin: 0 auto;
        width: 27.6rem;
        height: 1.6rem;
      }

      .tag {
        position: absolute;
        width: 8.2rem;
        height: 8.2rem;
        top: -3rem;
        left: 6.5rem;
        background-image: url("https://rwstatic.tentons.cn/web/Lesson/images/sentence-tag.png");
        background-size: contain;
        background-repeat: no-repeat;
      }
    }
  }

  .evaluate-line {
    height: 5.4rem;
  }

  .evaluate-popup-content {
    padding: 1.6rem 2rem;
    border-top: 0.15rem solid $uni-text-color;
    border-top-left-radius: 3rem;
    border-top-right-radius: 3rem;
    background-color: #fff;

    .popup-close {
      float: right;
      width: 2.4rem;
      height: 2.4rem;
    }

    .popup-title {
      display: flex;
      align-items: center;
      margin-bottom: 2rem;
      clear: both;
      font-family: xiaolai;
      font-size: 1.6rem;
      color: $uni-text-color;

      .popup-title-label {
        margin-left: 0.8rem;
        font-family: xiaolai;
        font-size: 1.2rem;
        color: $uni-text-color-grey;
      }
    }

    .popup-words {
      display: inline-block;
      margin-bottom: 1.2rem;

      .word {
        display: inline-block;
      }
    }

    .popup-sound {
      padding: 0.8rem 1.2rem;
      border-radius: 1rem;
      background-color: rgba(#fae4bd, 0.2);

      .sound-row {
        margin-bottom: 0.6rem;
        font-family: xiaolai;
        font-size: 1.4rem;
        color: $uni-text-color;

        .sound {
          display: inline-block;
          margin-left: 0.5rem;
          color: $uni-text-color-grey;
        }
      }
    }

    .popup-label {
      display: flex;
      align-items: center;
      justify-content: space-evenly;
      margin-top: 1rem;

      .label-item {
        display: flex;
        align-items: center;

        .Awesome {
          background-color: #b0bd3b;
        }

        .Good {
          background-color: #7eb6e6;
        }

        .Average {
          background-color: #ffaf00;
        }

        .Wrong {
          background-color: $uni-text-color-error;
        }

        .label-text {
          font-size: 1rem;
          font-family: xiaolai;
          color: #a87f71;
        }

        .label-tag {
          width: 0.84rem;
          height: 0.84rem;
          margin-right: 0.33rem;
          border-radius: 50%;
        }
      }
    }

    .popup-line {
      height: 3rem;
    }
  }
}
</style>